package com.aceitunaproject.webclient.client;

//import java.util.Date;
import java.util.List;

import com.aceitunaproject.shared.gamelement.Unit;
import com.aceitunaproject.shared.map.MapTile;
import com.google.gwt.core.client.EntryPoint;
import com.google.gwt.core.client.GWT;
import com.google.gwt.user.client.rpc.AsyncCallback;
import com.google.gwt.user.client.ui.DialogBox;


/**
 * Entry point classes define <code>onModuleLoad()</code>.
 */
public class Aceituna_webclient implements EntryPoint, MainAceitunaClient {
	/**
	 * The message displayed to the user when the server cannot be reached or
	 * returns an error.
	 */
	private static final String SERVER_ERROR = "An error occurred while "
			+ "attempting to contact the server. Please check your network "
			+ "connection and try again.";

	/**
	 * Create a remote service proxy to talk to the server-side Greeting
	 * service.
	 */
	private final AceitunaServiceAsync aceitunaService = GWT
	.create(AceitunaService.class);

	
	private final MessageBox actionInProgressBox =  new MessageBox("Please Wait", "");
	private EnumOrder orderInProgress;

	private String clientID;

	private final Board board = new Board(this);

	/**
	 * This is the entry point method.
	 */
	@Override
	public void onModuleLoad() {
		new LoginBox(this);
	}

	public void refreshMap() {
		getAceitunaService().getMap(clientID,
				new AsyncCallback<List<MapTile>>() {

					@Override
					public void onFailure(Throwable caught) {
						MessageBox.showDialog("Remote Procedure Call - Failure",
								SERVER_ERROR);

					}

					@Override
					public void onSuccess(List<MapTile> result) {
						//movingBox.setHTML(movingBox.getHTML() + "<br> received map, displaying" + new Date().toString());
						board.Display(translateTiles(result));
						actionInProgressBox.hide();
						//movingBox.setHTML(movingBox.getHTML() + "<br> displayed map" + new Date().toString());
					}
				});

	}

	private static WebTile[] translateTiles(List<MapTile> tiles) {

		WebTile[] resultTiles = new WebTile[tiles.size()];
		int i = 0;
		for (MapTile theTile : tiles) {
			resultTiles[i] = new WebTile(theTile);
			i++;
		}

		// for (MapTile mapTile : tiles) {
		//
		// resultTiles[mapTile.getPosx()][mapTile.getPosy()]
		// .setBasicTileType(mapTile.getTerrain().get(0).getName());
		//
		// Settlement theSettlement = mapTile.getSettlement();
		// if (theSettlement != null) {
		// System.out.println("settlement!");
		// Thing t = new Thing("Settlement");
		// resultTiles[mapTile.getPosx()][mapTile.getPosy()].addThing(t);
		// }
		//
		// for (Installation installation : mapTile.getInstallations()) {
		// System.out.println("Installation!");
		// String instType = "";
		// if (installation.isComplete()) {
		// instType = "installation_" + installation.getType();
		// } else {
		// instType = "installation_Incomplete";
		// }
		// Thing t = new Thing(instType);
		// resultTiles[mapTile.getPosx()][mapTile.getPosy()].addThing(t);
		// }
		//
		// for (int i = 0; i < mapTile.getUnits().size(); i++) {
		//
		// Thing t = new Thing("unit");
		// resultTiles[mapTile.getPosx()][mapTile.getPosy()].addThing(t);
		// }
		//
		// }

		return resultTiles;
	}

	@Override
	public AceitunaServiceAsync getAceitunaService() {
		return aceitunaService;
	}

	@Override
	public void setClientId(String clientId) {
		this.clientID = clientId;

	}

	@Override
	public String getClientId() {
		return clientID;
	}

	@Override
	public void UserLoggedIn(String userName) {
		refreshMap();

	}

	@Override
	public void orderedToRefreshMap() {
		refreshMap();

	}

	@Override
	public void orderedToCancel() {
		setOrderInProgress(null);
		

	}

	@Override
	public void orderedToBuildSettlement() {
		setOrderInProgress(EnumOrder.BuildSettlement);
		actionInProgressBox.getTextlabel().setText("Moving Unit");
		actionInProgressBox.center();
//		movingBox.setHTML("");
//		movingBox.setHTML(movingBox.getHTML() + "<br> user ordered move " + new Date().toString());
		Unit theUnit = board.GetElementDetails().getSelectedUnit();
		 new DialogBox(true,true).center();
		aceitunaService.BuildSettlement(clientID, theUnit.getId() ,theUnit.getName(),theUnit.getPositionX(),theUnit.getPositionY(),
				new AsyncCallback<Void>() {

					@Override
					public void onSuccess(Void result) {
						
						//movingBox.setHTML(movingBox.getHTML() + "<br> move executed" + new Date().toString());
						refreshMap();
						
						
					}

					@Override
					public void onFailure(Throwable caught) {
						MessageBox.showDialog("Alert - Service Failure",
								caught.getMessage());

					}
				});

	}

	@Override
	public void orderedToBuildInstallation() {
		// TODO Auto-generated method stub

	}

	@Override
	public void orderedToAttackWithUnit() {
		// TODO Auto-generated method stub

	}

	@Override
	public void orderedToBuildUnit() {
		// TODO Auto-generated method stub

	}

	@Override
	public void orderedToMoveUnit() {
		setOrderInProgress(EnumOrder.MoveUnit);
		board.DisplayMessage("Select Unit Destination");

	}

	@Override
	public void MoveUnit(Unit selectedUnit, MapTile mapTile) {

		actionInProgressBox.getTextlabel().setText("Moving Unit");
		actionInProgressBox.center();
//		movingBox.setHTML("");
//		movingBox.setHTML(movingBox.getHTML() + "<br> user ordered move " + new Date().toString());
		aceitunaService.MoveUnit(clientID, selectedUnit.getId(),
				mapTile.getPosx(), mapTile.getPosy(),
				new AsyncCallback<Void>() {

					@Override
					public void onSuccess(Void result) {
						
						//movingBox.setHTML(movingBox.getHTML() + "<br> move executed" + new Date().toString());
						refreshMap();
						
						
					}

					@Override
					public void onFailure(Throwable caught) {
						MessageBox.showDialog("Alert - Service Failure",
								caught.getMessage());

					}
				});

	}

	/**
	 * @param orderInProgress the orderInProgress to set
	 */
	public void setOrderInProgress(EnumOrder orderInProgress) {
		this.orderInProgress = orderInProgress;
		if(orderInProgress != null)
		{
			board.getOrdersPanel().setForCancelOnly();
		}
		else
		{
			board.getOrdersPanel().setForNothing();
		}
	}

	/**
	 * @return the orderInProgress
	 */
	public EnumOrder getOrderInProgress() {
		return orderInProgress;
	}

}
